﻿/************************************************************************

   Extended Silverlight Toolkit

   Copyright (C) 2010-2012 Xceed Software Inc.

   This program is provided to you under the terms of the Microsoft Public
   License (Ms-PL) as published at http://extendedsilverlight.codeplex.com/license

   Please purchase a commercial version of this toolkit if you are using
   it in a commercial product. The commercial versions support the project,
   and also include more features for each control, priority support,
   source code, updates, removed watermark, and a proprietary license.

   Visit http://xceed.com and follow @datagrid on Twitter.

  **********************************************************************/

using System;
using System.Windows;
using System.Collections.Generic;
using System.Linq;

namespace Xceed.Silverlight.DataGrid
{
  internal class ColumnInnerPanel : ILayoutContainer
  {
    public ColumnInnerPanel()
    {
      m_layout = EmptyLayout.Instance;
    }

    public ILayout Layout
    {
      get { return m_layout; }
    }

    private LayoutUpdateResult SetLayoutCore( ILayout oldLayout, ILayout newLayout )
    {
      if( oldLayout == null )
        throw new ArgumentNullException( "oldLayout" );

      if( newLayout == null )
        throw new ArgumentNullException( "newLayout" );

      IEnumerable<ILayoutElement> addedElements = newLayout.Elements.Except( oldLayout.Elements ).ToList();
      IEnumerable<ILayoutElement> removedElements = oldLayout.Elements.Except( newLayout.Elements ).ToList();

      return new LayoutUpdateResult( addedElements, removedElements );
    }

    internal LayoutUpdateResult SetLayout( ILayout layout )
    {
      if( m_previousLayout != null )
        throw new DataGridInternalException();

      m_previousLayout = m_layout;
      m_layout = layout;

      return this.SetLayoutCore( m_previousLayout, m_layout );
    }

    internal void CommitLayout()
    {
      m_previousLayout = null;
    }

    internal LayoutUpdateResult RollbackLayout()
    {
      if( m_previousLayout == null )
        return LayoutUpdateResult.Empty;

      LayoutUpdateResult result = this.SetLayoutCore( m_layout, m_previousLayout );

      m_layout = m_previousLayout;
      m_previousLayout = null;

      return result;
    }

    internal virtual void EndTransition()
    {
      // Since the layout "EndTransition" call will remove
      // some columns that are rendered out-of-view, it is important
      // to clean up all the rendered elements first.
      foreach( ColumnContainer column in this.Layout.Elements )
      {
        LayoutTransitionHelper.EndTransition( column );
      }
    }

    public void MeasureElement( ILayoutElement element, Size availableSize )
    {
      element.Measure( availableSize );
    }

    public void ArrangeElement( ILayoutElement element, Rect finalPosition, LayoutParameters parameters )
    {
      element.Arrange( new ArrangeParameters( finalPosition, parameters ) );
    }

    private ILayout m_layout;
    private ILayout m_previousLayout;
  }
}
